/*
 * Project Beknyou
 * Copyright (c) 2010-2011 Saint Paul College, All Rights Reserved
 * Redistributions in source code form must reproduce the above
 * Copyright and this condition.
 * The contents of this file are subject to the GNU General Public
 * License, Version 2 (the "License"); you may not use this file
 * except in compliance with the License. A copy of the License is
 * available at http://www.opensource.org/licenses/gpl-license.php.
*/
package com.benkyou.server;

import com.benkyou.common.messages.VNCMessage;
import com.glavsoft.viewer.Viewer;
import com.glavsoft.viewer.cli.Parser;
import com.glavsoft.viewer.swing.ParametersHandler;
import com.sun.image.codec.jpeg.JPEGCodec;
import com.sun.image.codec.jpeg.JPEGImageEncoder;
import java.awt.Graphics2D;
import java.awt.Image;
import java.awt.image.BufferedImage;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.swing.SwingUtilities;
import com.benkyou.util.ByteArrayList;
import com.jme3.network.serializing.Serializer;
import com.sun.image.codec.jpeg.JPEGImageDecoder;
import java.io.ByteArrayInputStream;
import java.util.ArrayList;

/**
 *
 * @author Austin Allman
*/
public class VNCServer {

    private Thread broadcast;
    private String[] serverLocation = {"199.17.224.133", "5900"};
   // private String[] serverLocation = {"192.168.22.217", "5900"};
    private ByteArrayList byteArrayList = new ByteArrayList();
    private Viewer viewer;
    private BufferedImage decodedImage;
    private GameServer gameServer;
    public static ArrayList<byte[]> desktopImageBytes = new ArrayList<byte[]>();

    public VNCServer(GameServer gameServer) {
        Serializer.registerClass(VNCMessage.class);
        this.gameServer = gameServer;

        startViewer();
        try {
            Thread.sleep(1000);
            //hideDesktop();
        } catch (InterruptedException ex) {
        }
    }

    public static void main(String args[]) {
    }

    public void setupBroadcaster() {
        broadcast = new Thread(new Runnable() {
            
            public void run() {
                 try {
                while (!Thread.currentThread().isInterrupted() && viewer != null && viewer.getDesktopImage() != null) {
                   
                        int numberOfParts = 0;
                        int imageID = (int) (Math.random() * 100);
                        int imageNumber = 0;
                        desktopImageBytes = byteArrayList.divideArrayList(byteArrayList.MESSAGE_LIMIT, getBufferedImageBytes(viewer.getDesktopImage()));
                        // public VNCMessage(byte[] b, int numberOfParts, int imageNumber, int imageID) {
                        numberOfParts = desktopImageBytes.size();
                  
                        for (byte[] b : desktopImageBytes) {
  
                            gameServer.getMyServer().broadcast(new VNCMessage(b, numberOfParts, imageNumber, imageID).setReliable(false));
                            // vncServer.broadcast(new VNCMessage());
                            imageNumber++;
                        }

                
                }
                    } catch (Exception ex) {
                        System.out.println("Unable to connect to vnc server with ip:" + serverLocation[0]);
                        System.out.println("Please restart server to enable vnc servers");
                        //Logger.getLogger(VNCServer.class.getName()).log(Level.SEVERE, null, ex);
                    }
            }
        
        });
       

    }
    

    public void startBroadcast() {
        broadcast.start();

    }

    public void stopBroadcast() {
        try {
            broadcast.interrupt();
        } catch (Exception e) {
        }
    }

    public void startViewer() {
        Parser parser = new Parser();
        ParametersHandler.completeParserOptions(parser);

        parser.parse(serverLocation);
        viewer = new Viewer(parser);
       SwingUtilities.invokeLater(viewer);
 
    }

    public BufferedImage imageToBufferedImage(Image image) {
        Image desktopImage = image;
        BufferedImage desktopBufferedImage = new BufferedImage(desktopImage.getWidth(null), desktopImage.getHeight(null), BufferedImage.TYPE_INT_RGB);
        Graphics2D g = desktopBufferedImage.createGraphics();
        g.drawImage(desktopImage, null, null);
        return desktopBufferedImage;
    }

    public byte[] getBufferedImageBytes(Image bufferedImage) throws IOException {
        ByteArrayOutputStream os = new ByteArrayOutputStream();
        JPEGImageEncoder encoder = JPEGCodec.createJPEGEncoder(os);
        encoder.encode((BufferedImage) bufferedImage);
        return os.toByteArray().clone();
    }

    public BufferedImage decodeStream(byte[] bytesToDecode) throws IOException {
        ByteArrayInputStream is = new ByteArrayInputStream(bytesToDecode);
        JPEGImageDecoder decoder = JPEGCodec.createJPEGDecoder(is);
        decodedImage = decoder.decodeAsBufferedImage();
        return decodedImage;
    }

    public Viewer getViewer() {
        return viewer;
    }

    public void hideDesktop() {
        //viewer.hideContainer();
    }

    public void showDesktop() {
        //viewer.showContainer();
    }
}
